Working with Text, Buttons, Images, and Input Fields in Android
Course: Android App Development
Topic: Working with Text, Buttons, Images, and Input Fields
Course Link: Android App Development Course
Demo Link: Register for a Free Course Demo
Website: JustAcademy
1. Introduction
Android applications use different user interface (UI) components to display information, accept user input, and perform actions. Text, buttons, images, and input fields are among the most commonly used components in Android development.
For example, a login screen displays labels using text components, accepts a username and password through input fields, provides a Login button, and may display a company logo using an image component.
Android developers can create these interfaces using traditional XML layouts with Android Views or by using Jetpack Compose, Android's modern declarative UI toolkit. This topic introduces both approaches so that developers can understand existing Android projects and build modern applications.
2. Learning Objectives
- Understand the role of text, buttons, images, and input fields.
- Use TextView and Button in XML-based Android layouts.
- Create text, buttons, images, and input fields using Jetpack Compose.
- Handle button click events and user interactions.
- Read, validate, and process user-entered information.
- Display images using drawable resources and image-loading components.
- Apply styling, accessibility, and responsive UI practices.
- Build a simple form using multiple Android UI components.
3. Understanding Android UI Components
A UI component is an element displayed on the screen that either presents information or allows the user to interact with an application.
| Component |
Traditional Android View |
Jetpack Compose |
Purpose |
| Text |
TextView |
Text() |
Displays labels, messages, titles, and descriptions. |
| Button |
Button |
Button() |
Performs an action when clicked. |
| Image |
ImageView |
Image() |
Displays logos, icons, illustrations, and photographs. |
| Input field |
EditText |
TextField() |
Accepts text, passwords, email addresses, and other user input. |
4. Working with Text in Android
4.1 What Is TextView?
TextView is a traditional Android View used to display text on the screen. It is commonly used for headings, descriptions, labels, instructions, status messages, and informational content.
TextView generally displays information rather than accepting editable user input. For editable content, Android applications typically use EditText.
4.2 Creating a TextView Using XML
To create a TextView, declare the component inside an Android layout file, such as activity_main.xml.
<TextView
android:id="@+id/tvWelcome"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Welcome to Android Development"
android:textSize="22sp"
android:textStyle="bold"
android:textColor="#212121"
android:padding="12dp" />
Explanation:
android:id assigns an identifier to the component.
android:layout_width defines the component's width.
android:layout_height defines the component's height.
android:text specifies the displayed text.
android:textSize controls the font size.
android:textStyle applies styling such as bold or italic.
android:textColor specifies the text color.
android:padding adds space between the text and the component's content boundary.
4.3 Displaying Text Using Jetpack Compose
Jetpack Compose uses the Text() composable to display text. A composable is a Kotlin function that describes part of the user interface.
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.unit.sp
@Composable
fun WelcomeText() {
Text(
text = "Welcome to Android Development",
modifier = Modifier,
fontSize = 22.sp,
fontWeight = FontWeight.Bold,
color = Color.DarkGray
)
}
In Compose, the Text() function displays content, while properties such as fontSize, fontWeight, and color control its appearance.
4.4 Text Styling and Formatting
Text styling improves readability and helps establish a clear visual hierarchy. Titles should generally appear more prominent than descriptions or secondary labels.
| Property |
Purpose |
Example |
| textSize / fontSize |
Controls text size. |
18sp |
| textColor / color |
Sets text color. |
Dark gray |
| textStyle / fontWeight |
Changes text emphasis. |
Bold |
| textAlignment / textAlign |
Controls text alignment. |
Center |
| maxLines |
Limits the displayed lines. |
2 |
| fontFamily |
Specifies a font family. |
Sans-serif |
4.5 Best Practices for Text
- Use clear and meaningful labels.
- Choose readable font sizes and maintain sufficient color contrast.
- Use string resources instead of hardcoding user-facing text in production XML layouts.
- Support longer translated strings and different screen sizes.
- Avoid displaying important information exclusively through color.
- Use scalable text units such as sp for font sizes.
5. Working with Buttons in Android
5.1 What Is a Button?
A Button is an interactive UI component that lets users trigger an action. Common examples include Login, Submit, Register, Save, Search, and Cancel.
Buttons usually execute code when a user taps them. That code might validate a form, navigate to another screen, save information, or display a message.
5.2 Creating a Button Using XML
<Button
android:id="@+id/btnSubmit"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Submit"
android:contentDescription="Submit form" />
The button has a unique identifier and a visible label. Android's standard Button component already exposes its label to accessibility services, so a redundant content description is generally unnecessary for a text button. Provide a content description when it adds useful information, particularly for icon-only controls.
5.3 Handling Button Clicks in Kotlin
For a traditional XML-based interface, use setOnClickListener() to respond to button taps.
import android.os.Bundle
import android.widget.Button
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val submitButton = findViewById<Button>(R.id.btnSubmit)
submitButton.setOnClickListener {
Toast.makeText(
this,
"Form submitted successfully",
Toast.LENGTH_SHORT
).show()
}
}
}
Explanation:
setContentView() loads the XML layout.
findViewById() retrieves the button from that layout.
setOnClickListener() registers a click callback.
Toast.makeText() creates a short notification.
show() displays the Toast message.
5.4 Creating a Button Using Jetpack Compose
import androidx.compose.material3.Button
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.platform.LocalContext
import android.widget.Toast
@Composable
fun SubmitButton() {
val context = LocalContext.current
Button(
onClick = {
Toast.makeText(
context,
"Form submitted successfully",
Toast.LENGTH_SHORT
).show()
}
) {
Text("Submit")
}
}
In Compose, the onClick parameter defines what happens when the user presses the button. The Text composable inside the Button supplies its visible label.
5.5 Button States
Buttons may have different states depending on user interaction and application logic.
- Enabled: The button can be clicked.
- Disabled: The button cannot currently be activated.
- Pressed: The user is interacting with the button.
- Loading: The application is processing an operation and may temporarily prevent repeated submissions.
In Jetpack Compose, a button can be disabled by setting enabled = false. In a real application, show a loading indicator during lengthy operations and restore the button appropriately when processing finishes.
6. Working with Images in Android
6.1 What Is ImageView?
ImageView is a traditional Android View that displays image resources. It is useful for application logos, profile pictures, product photographs, illustrations, and other visual content.
6.2 Adding Images to Android Resources
- Prepare an image in a suitable format, such as PNG or WebP.
- Place the image in the appropriate Android resource directory, commonly
res/drawable.
- Use a lowercase resource filename with underscores if needed, such as
app_logo.png.
- Reference the image in an ImageView or another supported image component.
6.3 Creating an ImageView Using XML
<ImageView
android:id="@+id/imgLogo"
android:layout_width="120dp"
android:layout_height="120dp"
android:src="@drawable/app_logo"
android:scaleType="fitCenter"
android:contentDescription="Application logo" />
Important attributes:
android:src identifies the image resource.
android:scaleType determines how the image is scaled within the view.
android:contentDescription provides an accessible description when the image conveys meaningful information.
android:layout_width and android:layout_height control the view dimensions.
For purely decorative images, use an appropriate empty accessibility description so screen readers can skip them when the framework and layout support that behavior.
6.4 Displaying Images Using Jetpack Compose
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.size
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.unit.dp
@Composable
fun AppLogo() {
Image(
painter = painterResource(id = R.drawable.app_logo),
contentDescription = "Application logo",
modifier = Modifier.size(120.dp),
contentScale = ContentScale.Fit
)
}
The painterResource() function loads a local drawable resource, while contentScale controls how the image fits its display area.
6.5 Common Image Scaling Options
| Option |
Behavior |
Common Use |
| FitCenter / ContentScale.Fit |
Fits the entire image inside the available area while preserving its aspect ratio. |
Logos and illustrations. |
| CenterCrop / ContentScale.Crop |
Fills the area while preserving aspect ratio, cropping excess edges. |
Profile photos and thumbnails. |
| CenterInside / ContentScale.Inside |
Keeps the complete image visible and avoids enlarging it beyond its original dimensions. |
Small icons or illustrations. |
| FillBounds / ContentScale.FillBounds |
Stretches the image to fill the area, potentially changing its proportions. |
Only when stretching is acceptable. |
6.6 Best Practices for Images
- Use appropriately sized assets to reduce memory usage.
- Prefer vector drawables for simple scalable icons when suitable.
- Provide meaningful accessibility descriptions for informative images.
- Choose the correct scaling behavior to avoid unwanted cropping or distortion.
- Use an image-loading library such as Coil when loading remote images in Compose.
- Handle unavailable images and loading failures gracefully.
7. Working with Input Fields in Android
7.1 What Is EditText?
EditText is a traditional Android UI component that allows users to enter and edit text. It is commonly used for names, email addresses, passwords, search queries, phone numbers, and comments.
In Jetpack Compose, TextField and OutlinedTextField provide editable text input. The application maintains the input value in state and updates it as the user types.
7.2 Creating an EditText Using XML
<EditText
android:id="@+id/etName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="Enter your name"
android:inputType="textPersonName"
android:singleLine="true"
android:padding="12dp" />
Explanation:
android:hint displays a temporary prompt when the field is empty.
android:inputType suggests the expected kind of input and helps configure the keyboard.
android:singleLine configures single-line entry in traditional layouts; use appropriate modern single-line configuration where needed.
android:padding provides space inside the field.
7.3 Common Input Types
| Input Type |
XML Example |
Purpose |
| Person name |
textPersonName |
Entering a person's name. |
| Email address |
textEmailAddress |
Entering an email address. |
| Password |
textPassword |
Entering a concealed text password. |
| Phone number |
phone |
Entering a phone number. |
| Numeric value |
number |
Entering a numeric value. |
| Multiline text |
textMultiLine |
Entering a longer message or description. |
7.4 Reading Input from EditText
import android.os.Bundle
import android.widget.Button
import android.widget.EditText
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val nameInput = findViewById<EditText>(R.id.etName)
val submitButton = findViewById<Button>(R.id.btnSubmit)
submitButton.setOnClickListener {
val name = nameInput.text.toString().trim()
if (name.isEmpty()) {
nameInput.error = "Name is required"
} else {
Toast.makeText(
this,
"Welcome, $name!",
Toast.LENGTH_SHORT
).show()
}
}
}
}
This example reads the entered name, removes leading and trailing whitespace, and checks whether the field is empty. If it is empty, the application displays an error. Otherwise, it displays a personalized greeting.
7.5 Creating an Input Field Using Jetpack Compose
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.OutlinedTextField
import androidx.compose.material3.Text
import androidx.compose.runtime.*
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
@Composable
fun NameInput() {
var name by remember { mutableStateOf("") }
Column(
modifier = Modifier.padding(16.dp)
) {
OutlinedTextField(
value = name,
onValueChange = { name = it },
label = { Text("Name") },
placeholder = { Text("Enter your name") },
modifier = Modifier.fillMaxWidth(),
singleLine = true
)
}
}
How it works:
remember preserves the value across recompositions for the current composition.
mutableStateOf("") creates observable state with an initial empty string.
value = name displays the current input value.
onValueChange updates the state whenever the user changes the text.
label identifies the field, and placeholder provides an example or hint.
For input that must survive activity recreation or configuration changes, consider rememberSaveable or state managed by a ViewModel, depending on the application's requirements.
7.6 Input Validation
Input validation checks whether the supplied information meets the application's requirements before processing it. Validation improves the user experience and prevents incomplete or incorrectly formatted information from being submitted.
Common validation rules include:
- A required name must not be empty.
- An email address should follow an acceptable email format.
- A password must satisfy the application's security requirements.
- A phone number must be checked according to the applicable format.
- Numeric values should be within an acceptable range.
Example of basic validation in Jetpack Compose:
import androidx.compose.foundation.layout.Column
import androidx.compose.material3.Button
import androidx.compose.material3.OutlinedTextField
import androidx.compose.material3.Text
import androidx.compose.runtime.*
import androidx.compose.ui.Modifier
@Composable
fun ValidatedNameForm() {
var name by remember { mutableStateOf("") }
var submitted by remember { mutableStateOf(false) }
val isValid = name.trim().isNotEmpty()
Column {
OutlinedTextField(
value = name,
onValueChange = {
name = it
submitted = false
},
label = { Text("Name") },
isError = submitted && !isValid,
supportingText = {
if (submitted && !isValid) {
Text("Please enter your name")
}
}
)
Button(
onClick = { submitted = true }
) {
Text("Submit")
}
if (submitted && isValid) {
Text("Name submitted successfully")
}
}
}
This example validates the name when the user taps Submit. It shows an error message for empty input and a success message when the name is valid. A production application should also perform appropriate validation on the server when information is sent to a backend.
8. Combining Text, Buttons, Images, and Input Fields
Most practical Android screens combine multiple UI components to create a complete user experience. A registration screen, for example, can include a logo, heading, name field, email field, and submit button.
8.1 Complete Jetpack Compose Example
The following example combines all four component types into a simple profile form. It uses a local drawable named app_logo, which should exist in the application's drawable resources.
import android.widget.Toast
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.size
import androidx.compose.material3.Button
import androidx.compose.material3.OutlinedTextField
import androidx.compose.material3.Text
import androidx.compose.runtime.*
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
@Composable
fun ProfileForm() {
var name by remember { mutableStateOf("") }
var email by remember { mutableStateOf("") }
var submitted by remember { mutableStateOf(false) }
val context = LocalContext.current
val validName = name.trim().isNotEmpty()
val validEmail = android.util.Patterns.EMAIL_ADDRESS
.matcher(email.trim())
.matches()
Column(
modifier = Modifier
.fillMaxWidth()
.padding(20.dp),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.spacedBy(12.dp)
) {
Image(
painter = painterResource(
id = R.drawable.app_logo
),
contentDescription = "Application logo",
modifier = Modifier.size(100.dp)
)
Text(
text = "Create Your Profile",
fontSize = 24.sp,
fontWeight = FontWeight.Bold
)
OutlinedTextField(
value = name,
onValueChange = { name = it },
label = { Text("Full Name") },
modifier = Modifier.fillMaxWidth(),
singleLine = true,
isError = submitted && !validName
)
OutlinedTextField(
value = email,
onValueChange = { email = it },
label = { Text("Email Address") },
modifier = Modifier.fillMaxWidth(),
singleLine = true,
isError = submitted && !validEmail
)
if (submitted && !validName) {
Text("Please enter your name")
}
if (submitted && !validEmail) {
Text("Please enter a valid email address")
}
Button(
onClick = {
submitted = true
if (validName && validEmail) {
Toast.makeText(
context,
"Profile form is valid",
Toast.LENGTH_SHORT
).show()
}
},
modifier = Modifier.fillMaxWidth()
) {
Text("Submit")
}
}
}
8.2 Understanding the Example
- Image: Displays the application logo using a drawable resource.
- Text: Shows the heading Create Your Profile.
- Name input: Accepts the user's full name.
- Email input: Accepts an email address.
- Button: Triggers the form validation process.
- State management: Stores the current field values and whether submission has been attempted.
- Validation: Checks that the name is not empty and that the email follows a recognizable email format.
- Feedback: Displays validation errors or a success Toast.
Note that an email-format check does not prove that an email address exists. Real applications may need verification through an email confirmation workflow and backend services.
9. Improving UI Design and User Experience
9.1 Layout and Spacing
Use suitable layout components to arrange UI elements consistently. In XML-based interfaces, common layout containers include LinearLayout, FrameLayout, and ConstraintLayout. In Compose, use Row, Column, Box, and other layout composables.
- Use consistent spacing between related components.
- Keep form fields aligned and easy to scan.
- Use adequate touch targets for interactive controls.
- Avoid fixed dimensions that cause content to overflow on small screens.
- Allow the layout to adapt to screen sizes and orientation changes.
9.2 Colors and Typography
Choose colors and text styles that maintain a clear visual hierarchy. Important headings should be distinguishable from supporting text, while buttons should have enough contrast to communicate their purpose.
9.3 Accessibility
- Provide meaningful labels for input fields.
- Use descriptive text for buttons rather than vague labels such as Click Here.
- Supply content descriptions for informative images.
- Ensure that text remains readable when users increase system font size.
- Do not communicate validation errors through color alone; include explanatory text.
- Check that interactive components can be used with accessibility services.
9.4 Keyboard Management
When users focus on an input field, Android displays an appropriate keyboard. The input type should match the expected information. For example, email fields should request an email-friendly keyboard, while numeric fields should request a numeric keyboard when appropriate.
Forms with multiple fields should also support convenient focus movement, appropriate keyboard actions, and scrolling when the keyboard covers part of the screen.
10. Common Errors and Troubleshooting
| Problem |
Possible Cause |
Solution |
| Text does not appear. |
Incorrect resource, color, or visibility setting. |
Check the text value, text color, and component visibility. |
| Button click does nothing. |
Click listener is missing or not connected. |
Verify the listener or Compose onClick callback. |
| Image fails to load. |
Missing drawable or incorrect resource name. |
Check the resource directory and generated R reference. |
| Image looks stretched. |
Incorrect scaling behavior. |
Use a suitable scaleType or ContentScale setting. |
| Input value is always empty. |
Incorrect state handling or incorrect view reference. |
Verify the input identifier and read the current state or field value. |
| Validation does not work. |
Incorrect conditions or whitespace is not handled. |
Trim input where appropriate and test valid and invalid cases. |
| Keyboard covers a field. |
Layout does not account for the keyboard. |
Use appropriate window insets, scrolling, and keyboard handling. |
| Composable shows outdated data. |
UI is not observing the correct state. |
Use Compose state and update it through the appropriate callbacks. |
11. Best Practices for Android UI Development
- Use reusable composable functions or reusable XML components to avoid duplicated UI code.
- Keep presentation logic separate from networking, database operations, and other business logic.
- Use string resources for user-facing text in production applications.
- Use appropriate dimensions and theme resources rather than repeating arbitrary values.
- Validate user input before submitting data.
- Prevent duplicate submissions during ongoing operations.
- Use state management patterns appropriate to the complexity of the application.
- Provide helpful error messages and visible feedback after user actions.
- Test screens on different screen sizes, Android versions, and font settings.
- Use secure handling for sensitive information such as passwords.
12. Practical Exercises
Exercise 1: Welcome Screen
Create a screen containing a heading, a short description, and a logo. Experiment with text sizes, colors, alignment, and spacing.
Exercise 2: Interactive Button
Add a button that displays a Toast message when clicked. Then change the button label and test its enabled and disabled states.
Exercise 3: User Input Form
Create a form that accepts a user's name and phone number. Validate both fields and display a suitable message when the user submits the form.
Exercise 4: Registration Form
Build a registration screen containing a logo, heading, name field, email field, password field, and Register button. Add input validation and clear error messages.
Exercise 5: Mini Project
Develop a basic profile creation screen using Jetpack Compose. Include an image, text components, input fields, a submit button, and validation. Ensure that the interface remains usable on smaller devices.
13. Interview Questions and Answers
Q1. What is TextView in Android?
TextView is a traditional Android View used to display text, including headings, labels, messages, and descriptions.
Q2. What is the purpose of a Button?
A Button allows the user to initiate an action, such as submitting a form, saving data, or opening another screen.
Q3. What is the difference between TextView and EditText?
TextView primarily displays text, whereas EditText allows users to enter and edit text.
Q4. What is the difference between ImageView and Image in Compose?
ImageView is a traditional Android View used in View-based layouts. Image is a Jetpack Compose composable used to display images within a declarative UI.
Q5. How do you handle button clicks in traditional Android development?
Use setOnClickListener() to register a callback that runs when the button is clicked.
Q6. How do you handle button clicks in Jetpack Compose?
Provide an action through the Button composable's onClick parameter.
Q7. What is the purpose of a hint in an input field?
A hint gives the user an example or instruction about the expected input when the field is empty.
Q8. What is input validation?
Input validation checks whether entered data meets specified requirements before the application processes or submits it.
Q9. What is the difference between remember and rememberSaveable?
remember retains state across recompositions while the current composition remains active. rememberSaveable can also preserve supported state across activity recreation and other saved-state restoration scenarios.
Q10. Why is accessibility important in Android UI development?
Accessibility helps people with different abilities understand and interact with an application through readable content, suitable labels, sufficient contrast, and assistive technologies.
Q11. What is ContentScale in Jetpack Compose?
ContentScale determines how an image is fitted, cropped, or stretched within its available display area.
Q12. Why should user input be validated on the backend as well?
Client-side validation improves usability, but it can be bypassed. Server-side validation helps enforce data rules and security requirements independently of the client application.
14. Quick Revision Checklist
- Understand TextView and Compose Text.
- Create buttons and implement click handlers.
- Load drawable resources and display images.
- Choose appropriate image scaling options.
- Use EditText and Compose TextField for user input.
- Read input values and implement validation.
- Manage Compose UI state correctly.
- Apply suitable spacing, typography, and colors.
- Follow accessibility and responsive design practices.
- Build and test a complete form combining all four components.
15. Conclusion
Text, buttons, images, and input fields are essential building blocks of Android user interfaces. Text components communicate information, buttons trigger actions, images provide visual context, and input fields collect information from users.
Developers should understand both traditional Android Views, such as TextView, Button, ImageView, and EditText, and modern Jetpack Compose components, such as Text, Button, Image, and TextField. By combining these components with proper state management, validation, accessibility, and responsive layouts, developers can create reliable and user-friendly Android applications.
16. Additional Learning Resources
Explore the Android App Development course to continue learning about Android layouts, activities, Jetpack Compose, user interaction, and application development.
Explore the course: Android App Development Training
Register for a demo: Book a Course Demo
Visit JustAcademy: www.justacademy.co